package com.xoms.admin.service.impl;

import java.util.ArrayList;
import java.util.List;

import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.alibaba.fastjson.JSON;
import com.xoms.admin.controller.res.bean.RProCheckBean;
import com.xoms.admin.controller.res.bean.RProCheckProInfoBean;
import com.xoms.admin.model.AccountBean;
import com.xoms.admin.model.AuditBean;
import com.xoms.admin.model.ProCheckBean;
import com.xoms.admin.model.ProCheckProInfoBean;
import com.xoms.admin.model.vo.BatchCheckBean;
import com.xoms.admin.persist.dao.ProAuditDao;
import com.xoms.admin.persist.dao.ProCheckDao;
import com.xoms.admin.persist.dao.ProStoreDao;
import com.xoms.admin.service.ProCheckService;
import com.xoms.admin.service.exception.ServiceException;
import com.xoms.admin.service.res.PageResult;
import com.xoms.util.AppTextUtil;
import com.xoms.util.DateTimeUtil;
import com.xoms.util.NumUtil;
import com.xoms.util.StringUtil;

@Service
public class ProCheckServiceImpl implements  ProCheckService {
	
	Logger logger = Logger.getLogger(this.getClass());
	
	@Autowired
	ProCheckDao proCheckImpl;
	
	@Autowired
	ProAuditDao proAuditImpl;

	@Autowired
	ProStoreDao proStoreImpl;

	@Override
	public PageResult<RProCheckBean> getChecks(AccountBean account, int page, int pageSize, String startTime,
			String endTime, String storeId, String key) {
		PageResult<RProCheckBean> result = new PageResult<RProCheckBean>();
		List<RProCheckBean> resList = new ArrayList<RProCheckBean>();
		int count = proCheckImpl.selectCount(key, storeId, startTime, endTime);
		if(count > 0) {
			//查询入库单列表
			List<ProCheckBean> lists = proCheckImpl.selectList(key, page, pageSize, storeId, startTime, endTime);
			if (lists != null) {
				RProCheckBean rb = null;
				for (ProCheckBean pur : lists) {
					rb=new RProCheckBean();
					rb=parse(pur);
					resList.add(rb);
				}
			}
		}
		result.setData(resList);
		result.setCount(count);
		return result;
	}
	
	/**
	 * 格式化数据
	 * @param pur
	 * @return
	 */
	private RProCheckBean parse(ProCheckBean check) {
		RProCheckBean res = new RProCheckBean();
		res.setAccount(check.getAccount());
		res.setAccountId(check.getAccountId());
		res.setCheckNo(check.getCheckNo());
		res.setCid(check.getCid());
		res.setRemark(check.getRemark());
		res.setStatus(check.getStatus());
		res.setStoreHouse(check.getStoreHouse());
		res.setStoreHouseId(check.getStoreHouseId());
		res.setCreateTime(DateTimeUtil.formatTimestamp(check.getCreateTime()));
		return res;
	}

	@Override
	public PageResult<RProCheckProInfoBean> getCheckDetails(AccountBean account, int page, int pageSize, String cid,
			int paging) {
		PageResult<RProCheckProInfoBean> result = new PageResult<RProCheckProInfoBean>();
		List<RProCheckProInfoBean> resList = new ArrayList<RProCheckProInfoBean>();
		int count = proCheckImpl.selectDetailCount(cid);
		if(count > 0) {
			//查询采购单列表
			List<ProCheckProInfoBean> lists = proCheckImpl.selectDetailList(cid, page, pageSize, paging);
			if (lists != null) {
				RProCheckProInfoBean rb = null;
				for (ProCheckProInfoBean pur : lists) {
					rb = new RProCheckProInfoBean();
					rb = parseDetail(pur);
					resList.add(rb);
				}
			}
		}
		result.setData(resList);
		result.setCount(count);
		return result;
	}
	
	/**
	 * 格式化详情数量
	 * @param pur
	 * @return
	 */
	private RProCheckProInfoBean parseDetail(ProCheckProInfoBean check) {
		RProCheckProInfoBean res = new RProCheckProInfoBean();
		res.setCategory(check.getCategory());
		res.setCheckId(check.getCheckId());
		res.setNumber(check.getNumber());
		res.setPrice(check.getPrice());
		res.setProduct(check.getProduct());
		res.setProductId(check.getProductId());
		res.setProductBar(check.getProductBar());
		res.setStoreNumber(check.getStoreNumber());
		res.setUnit(check.getUnit());
		return res;
	}

	@Transactional(rollbackFor = Exception.class)// 事务
	@Override
	public RProCheckBean edit(AccountBean account, String cid, String storeHouseId, String remark,
			String details, int isSubmit) {
		boolean flag = false;
		ProCheckBean data = new ProCheckBean();
		data.setStoreHouseId(storeHouseId);
		data.setRemark(remark);
		if (StringUtil.isEmpty(cid)) {// 新建
			cid = AppTextUtil.getPrimaryKey();// id
			data.setCid(cid);
			data.setAccountId(account.getAccid());
			
			data.setStatus(isSubmit);// 未提交审核

			// 采购编号：PK + YYYYMMDDHHmm + 0000001;一年百万数据？
			String maxNo = proCheckImpl.selectMaxCheckNoInYear();// 获取当年采购单最大数量
			int num = 0;
			if(!StringUtil.isEmpty(maxNo)) {
				num = NumUtil.toInt(maxNo.substring(maxNo.length() - 7, maxNo.length()), 0);
			}
			String checkNo = AppTextUtil.getRandomProNo("PK", (num + 1), 7);
			data.setCheckNo(checkNo);

			flag = proCheckImpl.insert(data) > 0;
			if (!flag) {
				throw new ServiceException("database_insert_fail","采购订单");
			}
			if(isSubmit == 2) { // 直接提交审核
				flag = submitAudit(account, data.getCid(), 3);
			}
		} else {
			data.setCid(cid);
			flag = proCheckImpl.update(data) > 0;// 更新数据库
			if (!flag) {
				throw new ServiceException("database_update_fail","采购订单");
			}
		}
		// 将采购商品详情信息批量更新到数据库
		if(!StringUtil.isEmpty(details)) { 
			flag = replaceBatchDetail(cid, details);
		}
		ProCheckBean res = proCheckImpl.selectOneById(cid);
		return parse(res);
	}
	
	/**
	 * 批量替换详情信息
	 * @param cid
	 * @param details
	 * @return
	 */
	private boolean replaceBatchDetail(String cid, String details) {
		boolean flag = false;
		// JSON转list
		List<BatchCheckBean> batch = JSON.parseArray(details, BatchCheckBean.class);
		for(BatchCheckBean check : batch) {
			check.setCheckId(cid);
			int status = NumUtil.toInt(check.getNumber(), 0) < NumUtil.toInt(check.getStoreNumber(), 0) 
						? 2 : NumUtil.toInt(check.getNumber(), 0) > NumUtil.toInt(check.getStoreNumber(), 0) ? 3 : 1;
			check.setStatus(status);
		}
		
		if(batch.size() > 0) {
			// 判断数量
			int detailCount = proCheckImpl.selectDetailCount(cid);
			if(detailCount > 0) {
				// 删除当前采购单下所有关联采购单详情
				flag = proCheckImpl.delDetails(cid) > 0;
				if (!flag) {
					throw new ServiceException("database_delete_fail", "盘库详情");
				}
			}
			flag = proCheckImpl.replaceBatchDetail(batch) > 0;
			if (!flag) {
				throw new ServiceException("database_insert_fail","盘库详情");
			}
		}
		return flag;
	}

	@Transactional(rollbackFor = Exception.class)// 事务
	@Override
	public boolean del(AccountBean account, String cid) {
		boolean flag = false;
		// 删除采购单前判断是否已提交，提交的采购单不能删除
		ProCheckBean purchase = proCheckImpl.selectOneById(cid);
		if(purchase == null) {// 采购单不存在
			throw new ServiceException("object_is_not_exist","采购单");
		}
		int status = NumUtil.toInt(purchase.getStatus(), 1);
		if(status != 1) {
			throw new ServiceException("object_is_submit", "采购单");
		}
		
		flag = proCheckImpl.del(cid) > 0;
		if (!flag) {
			throw new ServiceException("database_delete_fail", "入库单");
		}
		// 判断数量
		int detailCount = proCheckImpl.selectDetailCount(cid);
		if(detailCount > 0) {
			// 删除当前采购单下所有关联采购单详情
			flag = proCheckImpl.delDetails(cid) > 0;
			if (!flag) {
				throw new ServiceException("database_delete_fail", "入库单详情");
			}
		}
		return flag;
	}

	@Transactional(rollbackFor = Exception.class)// 事务
	@Override
	public boolean submitCheck(AccountBean account, String cid) {
		boolean flag = false;
		// 提交采购单前判断是否是待提交状态，提交的采购单不能多次提交
		ProCheckBean purchase = proCheckImpl.selectOneById(cid);
		if(purchase == null) {// 采购单不存在
			throw new ServiceException("object_is_not_exist","采购单");
		}
		int status = purchase.getStatus();
		if(status != 1 && status != 4) {
			throw new ServiceException("object_is_not_unsubmit", "采购单");
		}
		flag = proCheckImpl.updateSubmitStatus(cid, 2) > 0;// 更新采购单状态,1提交待审核
		if (!flag) {// 更新状态失败
			throw new ServiceException("database_update_fail","采购审核状态");
		}
		flag = submitAudit(account, cid, 3);
		return flag;
	}
	
	/**
	 * 提交审核
	 * @param account
	 * @param cid
	 * @return
	 */
	private boolean submitAudit(AccountBean account, String cid, int type) {
		boolean flag;
		AuditBean audit = new AuditBean();// 添加到审核表
		audit.setAid(AppTextUtil.getPrimaryKey());
		audit.setSubmitId(account.getAccid());
		audit.setType(type);// 审核类型：1采购2入库3盘库4损耗5充公6冲正7退货到供应商
		audit.setTargetId(cid);// 关联id
		// 审核编号：SH+ YYYYMMDDHHmm + 0000001;一年百万数据？
		String maxNo = proAuditImpl.selectMaxAuditNoInYear(type);// 获取当年审核单最大数量
		int num = 0;
		if(!StringUtil.isEmpty(maxNo)) {
			num = NumUtil.toInt(maxNo.substring(maxNo.length() - 7, maxNo.length()), 0);
		}
		String auditNo = AppTextUtil.getRandomProNo("SH", (num + 1), 7);
		audit.setAuditNo(auditNo);
		audit.setStatus(0);
		
		flag = proAuditImpl.insert(audit) > 0;
		if (!flag) {// 插入状态失败
			throw new ServiceException("database_insert_fail","采购审核提交");
		}
		return flag;
	}

	
}
